import {
  getHashString,
  getFirstHashString,
  InbizIcon,
  getOfficialPreview,
} from '@inbiz/utils';
import { useState, useEffect, useCallback, useRef, ReactElement } from 'react';
import styles from './index.less';
import { useNavigate } from 'react-router-dom';

export interface BreadCrumbProps {
  className?: string;
  style?: object;
  data: any[];
  onBreadItemClick: (e: any, item: any, index?: number) => void;
  nameKey?: string;
  children?: ReactElement | null;
  showHome?: boolean;
  onClickHome?: () => void;
  itemStyle?: object | ((item: any, index: number) => object);
}
export default function Breadcrumb(props: BreadCrumbProps) {
  const history = useNavigate();
  const showHome =
    props.showHome == null ? !!getHashString('home') : props.showHome;
  const { className, style, nameKey = 'folderName', children = null } = props;
  const scrollRef: { current: any } = useRef();
  const breadTr: { current: any } = useRef();
  const [startX, _startX] = useState<number>(0);
  const [startY, _startY] = useState<number>(0);
  const [viewData, $viewData] = useState<any[]>([])
  const onTouchMove = useCallback(
    (e: any) => {
      var moveEndX = e.changedTouches[0].pageX,
        moveEndY = e.changedTouches[0].pageY,
        X = moveEndX - startX,
        Y = moveEndY - startY;
      if (Math.abs(X) > Math.abs(Y) && X > 0) {
        // alert("left 2 right");
      } else if (Math.abs(X) > Math.abs(Y) && X < 0) {
        // alert("right 2 left");
      } else if (Math.abs(Y) > Math.abs(X) && Y > 0) {
        // alert("top 2 bottom");
        e.stopPropagation();
      } else if (Math.abs(Y) > Math.abs(X) && Y < 0) {
        // alert("bottom 2 top");
        e.stopPropagation();
      } else {
        // alert("just touch");
      }
    },
    [startX, startY],
  );
  const handleBreadItemClick = useCallback(
    (e: any, item: any, index: any) => {
      if (props.onBreadItemClick) {
        props.onBreadItemClick(e, item, index);
      }
    },
    [props.onBreadItemClick],
  );

  const handleBreadEllipsisClick = useCallback(
    (e: any, item: any, index: any) => {
      if (props.onBreadItemClick && item.ellipsis && item.children?.length) {
        let parent = item.children[item.children.length - 1]
        props.onBreadItemClick(e, parent, index);
      }
    },
    [props.onBreadItemClick],
  );

  const onClickHome = () => {
    if (props.onClickHome) {
      props.onClickHome();
    } else {
      let home = getHashString('home');
      if (home) {
        home = decodeURIComponent(home);
        if (home?.slice(0, 4) == 'http') {
          location.href = home;
        } else {
          let prefix = ''
          if (location.hash.startsWith('#/page')) {
            prefix = '/page'
          } else if (location.hash.startsWith('#/preview/page')) {
            prefix = '/preview/page'
          } else if (location.hash.startsWith('#/preview')) {
            prefix = '/preview'
          }
          history(`${prefix}${home}`);
        }
      }
    }
  };

  useEffect(() => {
    getData(props.data)
  }, [props.data])

  //计算数据
  const getData = useCallback((data: any[]): any => {
    let list: any[] = [...data];
    let windowWidth: number = scrollRef.current?.clientWidth - 20 || 0;
    if (showHome) {
      windowWidth -= 40
    }
    // 单字符宽度
    const size = 6;
    // 省略结束下标
    let endIndex: number = 0;
    // 数据猜想长度
    let wantLength = 0;
    // 计算面包屑首个宽度
    const firstLen = (getLength(data[0]?.folderName) || 0) * size + 15;
    wantLength += firstLen
    for (let i = data.length - 1; i > 0; i--) {
      // 单个面包屑字符长度
      let length: number = getLength(data[i]?.folderName) || 0;
      // 单个面包屑占用像素
      let oneLength: number = length * size + 15;
      wantLength += oneLength;
      if ((i == 1 && wantLength > windowWidth) || (i != 1 && wantLength > windowWidth - 28)) {
        endIndex = i;
        break;
      }
    }
    if (endIndex != 0 && list.length > 1) {
      /* --------- 宽度不足单行显示全，处理省略数据 ----------- */
      let end: any[] = list.slice(endIndex + 1);
      let ellipsis = {
        ellipsis: true,
        hasMore: end.length > 0,
        children: list.slice(1, endIndex + 1),
      };
      let newList: any[] = [list[0]];
      // 最后一层都不足显示全
      if (!end.length) {
        const rec = list[endIndex]
        let strLen = windowWidth - firstLen
        if (ellipsis.children?.length > 1) {
          strLen -= 28
        }
        rec.max = strLen
        end = [rec]
        ellipsis.children.pop()
      }
      if (ellipsis.children?.length) {
        newList = [...newList, ellipsis]
      }
      if (end?.length) {
        newList = [...newList, ...end]
      }
      $viewData(newList);
      return
    }
    $viewData(list);
  }, []);

  const getLength = (val: string) => {
    if (typeof val !== 'string') return 0
    const l = val.length
    let length = 0
    let i = 0
    while (i < l) {
      const re = /[^\u4E00-\u9FA5]/
      if (re.test(val.substring(i, i + 1))) {
        length += 1
      } else {
        length += 2
      }
      i += 1
    }
    return length
  }

  return (
    <div
      className={`${styles.BreadCrumb} ${className}`}
      onTouchStartCapture={(e) => {
        _startX(e.changedTouches[0].pageX);
        _startY(e.changedTouches[0].pageY);
      }}
      onTouchMoveCapture={onTouchMove}
      style={{
        padding: '0 15px',
        ...style,
      }}
    >
      <div className={styles.tablebox} ref={scrollRef}>
        <div ref={breadTr} className={styles.breadcrumbList}>
          {showHome ? (
            <span
              className={`${styles.fontIconWrap} ${styles.breadcrumbItem}`}
              key={'home'}
              onClick={onClickHome}
            >
              <InbizIcon className={styles.fontIcon} type="icon-ecm-home" />
            </span>
          ) : null}
          {viewData.map((item, index) => {
            if (item.ellipsis) {
              // 省略
              return (
                <span className={styles.breadcrumbItem} onClick={(e) => handleBreadEllipsisClick(e, item, index)}><InbizIcon type='icon-more1' /></span>
              )
            }
            return (
              <span
                key={index}
                className={styles.breadcrumbItem}
                onClick={(e) => handleBreadItemClick(e, item, index)}
                style={{ maxWidth: item.max }}
              >
                <span
                  className={item.max ? styles.breadcrumbItemEnd : ''}
                  style={
                    typeof props.itemStyle == 'function'
                      ? props.itemStyle(item, index)
                      : props.itemStyle
                  }
                >
                  {item[nameKey]}
                </span>
              </span>
            );
          })}
        </div>
      </div>
      {children}
    </div>
  );
}
